<?php

namespace App\Repository;


use App\Repository\Enum\ScopeEnum;
use App\User;
use Dingo\Api\Exception\StoreResourceFailedException;
use Illuminate\Support\Facades\Cache;

/**
 * 继承token的基类
 * Class UserTokenRepository
 * @package App\Repository
 */
class UserTokenRepository extends TokenRepository
{
    /**
     * @var
     */
    protected $code;
    /**
     * @var mixed
     */
    protected $wxAppId;
    /**
     * @var string
     */
    protected $wxLoginUrl;
    /**
     * @var mixed
     */
    protected $wxAppsecret;
    /**
     * @var User
     */
    public $user;

    /**
     * UserTokenRepository constructor.
     * @param $code
     */
    public function __construct($code)
    {
        $this->code = $code;
        $this->wxAppId = env('APPID');
        $this->wxAppsecret = env('APPSECRET');
        $this->wxLoginUrl = sprintf( env('WXLOGINURL') , $this->wxAppId, $this->wxAppsecret, $this->code['code'] );
    }

    /**
     * @return string
     */
    public function get()
    {
        $result = curl_get($this->wxLoginUrl);

        $wxResult = json_decode($result, true);

        if (empty($wxResult)){
            throw new StoreResourceFailedException('获取openid和session_key异常，或是微信内部错误', null, null, [], 10000);
        }else{
            $loginFail = array_key_exists('errcode', $wxResult);
            if ($loginFail){
                throw new StoreResourceFailedException($wxResult['errmsg'], null, null, [], $wxResult['errcode']);
            }else{
                //成功返回token
                return $this->grantToken($wxResult);
            }
        }
    }

    /**
     * 颁发令牌
     * 拿到openid
     * 检查openid是否存在，如果存在则不处理，不存在就新增一条记录. 并获取用户ID
     * 准备令牌，准备缓存数据，写入缓存  key : 令牌  value: 就是用户的信息 wxResult, uid , scope
     * 令牌返回客户端
     * @param $wxResult
     * @return string
     */
    private function grantToken($wxResult)
    {
        $openid = $wxResult['openid'];
        $user = UserRepository::getByOpenId($openid);
        if ($user){
            $uid = $user->id;
        }else{
            $uid = UserRepository::newUser($openid);
        }
        $cacheValue = $this->prepareCacheValue($wxResult, $uid);
        return $this->saveToCache($cacheValue);
    }

    /**
     * 拼装缓存数据值
     * @param $wxResult
     * @param $uid
     * @return mixed
     */
    private function prepareCacheValue($wxResult, $uid)
    {
        $cacheValue = $wxResult;
        $cacheValue['uid'] = $uid;
        $cacheValue['scope'] = ScopeEnum::USER ;
        return $cacheValue;
    }

    /**
     * 缓存储存数据
     * @param $cacheValue
     * @return string
     */
    private function saveToCache($cacheValue)
    {
        $key = self::genarateToken();// 获取 key
        $value = json_encode($cacheValue);
        //令牌的缓存时间就是缓存的是时间【分】
        Cache::put($key, $value, env('MINUTES'));
        return $key;
    }

}
